package com.wangjiacai.utils.web.filter;

import com.fasterxml.jackson.databind.ObjectMapper;
import com.wangjiacai.utils.enums.ResultEnum;
import com.wangjiacai.utils.web.properties.FilterProperties;
import com.wangjiacai.utils.web.service.RedisService;
import com.wangjiacai.utils.utils.ResultVOUtil;
import org.springframework.util.AntPathMatcher;

import javax.servlet.*;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

/*
 * @auther: wangjiacai
 *
 * @create: 2018-04-28 15:46:47
 */
public class TokenFilter implements Filter {

    private FilterProperties filterProperties;

    private RedisService redisService;

    private ObjectMapper objectMapper=new ObjectMapper();

    private AntPathMatcher antPathMatcher=new AntPathMatcher();

    public TokenFilter(FilterProperties filterProperties, RedisService redisService) {
        this.filterProperties = filterProperties;
        this.redisService = redisService;
    }

    @Override
    public void init(FilterConfig filterConfig) throws ServletException {

    }

    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        HttpServletRequest request = (HttpServletRequest) servletRequest;
        HttpServletResponse response = (HttpServletResponse) servletResponse;
        if(shouldFilter(request)){
            String token = request.getHeader("token");
            if((token==null||redisService.get(token)==null)){
                if(isBrowserGet(request)){
                    response.sendRedirect("/login");
                    return;
                }else {
                    response.setContentType("application/json;charset=UTF-8");
                    response.getWriter().write(objectMapper.writeValueAsString(ResultVOUtil.error(ResultEnum.ILLEGAL_USERS)));
                    return;
                }
            }
        }
        filterChain.doFilter(request,response);
    }

    @Override
    public void destroy() {

    }
    public boolean shouldFilter(HttpServletRequest request) {
        for(String freeUrl:filterProperties.getFreeUrl()){
            if(antPathMatcher.match(freeUrl,request.getRequestURI())){
                return false;
            }
        }
        for(String passUrl:filterProperties.getPassUrl()){
            if(antPathMatcher.match(passUrl,request.getRequestURI())){
                return false;
            }
        }
        if(request.getRequestURI().equals("/login")) return false;
        return true;
    }

    private boolean isAjaxRequest(HttpServletRequest request){
        String header = request.getHeader("X-Requested-With");
        boolean isAjax = "XMLHttpRequest".equals(header) ? true:false;
        return isAjax;
    }

    private boolean isBrowserGet(HttpServletRequest request){
        if(!request.getMethod().equals("GET")) return false;
        if(request.getHeader("Accept")==null||!request.getHeader("Accept").startsWith("text/html")) return false;
        return true;
    }
}
